package com.gsnd.briuppts.web.Interceptor;

import com.gsnd.briuppts.entity.BaseAccount;
import com.gsnd.briuppts.exception.PtsException;
import com.gsnd.briuppts.mapper.BaseAccountMapper;
import com.gsnd.briuppts.result.ResponseCode;
import com.gsnd.briuppts.service.BaseAccountService;
import com.gsnd.briuppts.utils.JwtUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

/**
 * @Description: JWT拦截验证
 * @Author: GX Cui
 * @Date 16:56 2024/6/22
 */
@Component
public class JwtInterceptor implements HandlerInterceptor {

    @Autowired
    BaseAccountService baseAccountService;

    @Override
    public boolean preHandle(HttpServletRequest request,
                             HttpServletResponse response,
                             Object handler) throws Exception {
        // 当请求方式预检请求时，不需要进行token验证
        String method = request.getMethod();
        if(method.equals("OPTIONS")){
            return true;//通过拦截
        }

        // 输出当前的handler是谁？
        System.out.println("当前拦截的处理器是："+handler);
        // token在什么地方？
        // 前端拿到之后可以以什么方式传给我们？http请求
        // 请求：请求行（不能放数据）、请求头、请求体（post的请求的数据）
        // 结论：前端是将token包装到请求头里面传递给服务器的

        // 1、从请求头中取出token的字符串
        String token = request.getHeader("token");
        // 2、验证token存在
        if(token == null || "".equals(token)){
            // 抛出 令牌不存在 的异常
            throw new PtsException(ResponseCode.TOKEN_NOT_EXIST);
        }
        // 3、验证token是否有效
        if(!JwtUtil.checkSign(token)){
            // 抛出 令牌无效 的异常
            throw new PtsException(ResponseCode.TOKEN_INVALID);
        }
        // 4、验证token里保存的数据是否正确（可以不验证）
        String userId = JwtUtil.getUserId(token);
        String name = (String)JwtUtil.getInfo(token).get("username");

        // 4.1 取出id验证 通过id查询出来的用户是否存在
        // 根据id查询一个用户
        BaseAccount user = baseAccountService.findByAccountId(userId);
        // 4.2 假设用户存在，和取出来的name进行比对看是否一致
        if(user == null){
            throw new PtsException(ResponseCode.DATA_VALIDATE_ERROR);
        }
        if(!user.getUsername().equals(name)){
            throw new PtsException(ResponseCode.DATA_VALIDATE_ERROR);
        }

        // request  session  application
        // 将验证之后的id临时保存在会话中
        HttpSession session = request.getSession();
        session.setAttribute("userId",userId);
        // 截止6.23，只需要id这个信息，如果后续需要其他信息，在这里进行修改即可

        return true;
    }
}
